/**
 * @file         stm32f411_task_led.c
 * @brief		led task
 * @details	    This file provides all the led task functions.
 * @author		lin jie
 * @date		    2024/6/23
 * @version	    v1.0
 * @par Copyright(c): 	lin jie
 */

#include "stm32f411_task_led.h"
#include "stm32f411_task_key.h"
#include "main.h"

#include "FreeRTOS.h"
#include "task.h"

#include <stdint.h>
#include <stdbool.h>

static void led_init(void);
static void led_task(void);
static void led_on(led_type_t led);
static void led_off(led_type_t led);
static void led_toggle(led_type_t led);

struct LedClass
{
    uint8_t led_state;
};

struct LedClass led_imp[LED_TYPE_MAX];

struct LedInterface led_interface = {
    .pfinit = led_init,
    .pftask = led_task,
    .pfon = led_on,
    .pfoff = led_off,
    .pftoggle = led_toggle,
};

/**
 * @brief  led task loop
 *
 * @param  void
 *
 * @retval void
 */
static void led_task(void)
{
    key_result_t result;
    result = key_interface.pfget_result();
    if (KEY_SHORT_PRESS == result)
    {
        led_interface.pftoggle(LED_BLUE);
    }
    else if (KEY_LONG_PRESS == result)
    {
        // blink 3 times
        for (int i = 0; i < 5; i++)
        {
            led_interface.pftoggle(LED_BLUE);
            vTaskDelay(200);
        }
    }
}

/**
 * @brief  led toggle
 *
 * @param  led type of led
 *
 * @retval void
 */
static void led_toggle(led_type_t led)
{
    if (false == led_imp[LED_BLUE].led_state)
    {
        led_imp[LED_BLUE].led_state = true;
        HAL_GPIO_WritePin(LED_BLUE_GPIO_Port, LED_BLUE_Pin, GPIO_PIN_SET);
    }
    else
    {
        led_imp[LED_BLUE].led_state = false;
        HAL_GPIO_WritePin(LED_BLUE_GPIO_Port, LED_BLUE_Pin, GPIO_PIN_RESET);
    }
}

/**
 * @brief  led off
 *
 * @param  led type of led
 *
 * @retval void
 */
static void led_off(led_type_t led)
{
    if (false == led_imp[LED_BLUE].led_state)
    {
        led_imp[LED_BLUE].led_state = true;
        HAL_GPIO_WritePin(LED_BLUE_GPIO_Port, LED_BLUE_Pin, GPIO_PIN_SET);
    }
}

/**
 * @brief  led on
 *
 * @param  led type of led
 *
 * @retval void
 */
static void led_on(led_type_t led)
{
    if (true == led_imp[LED_BLUE].led_state)
    {
        led_imp[LED_BLUE].led_state = false;
        HAL_GPIO_WritePin(LED_BLUE_GPIO_Port, LED_BLUE_Pin, GPIO_PIN_RESET);
    }
}

/**
 * @brief  led init function
 *
 * @param  void
 *
 * @retval void
 */
static void led_init(void)
{
    led_off(LED_BLUE);
}
